package utils.http;

import cn.hutool.core.util.ObjectUtil;
import com.alibaba.fastjson.JSON;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.apache.http.HttpHost;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.*;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.util.EntityUtils;

import java.io.IOException;
import java.util.*;

@Slf4j
public class HttpUtil {

	/**
	 * http get请求
	 */
	public static String sendHttpGet(String url, Map<String, Object> params, String proxyIp, String proxyPort) throws Exception {
		String result = null;
		CloseableHttpClient httpClient = HttpClients.createDefault();
		String charset = "UTF-8";

		// 2.判断用户是否传递了参数
		if (params != null) { // 如果有参数则需要字符串的拼接
			url += "?";
			StringBuilder urlBuilder = new StringBuilder(url);
			for (Map.Entry<String, Object> entry : params.entrySet()) {
				String key = entry.getKey();
				String value = "";
				if (ObjectUtil.isNotEmpty(entry.getValue())) {
					value = String.valueOf(entry.getValue());
				}
				urlBuilder.append(key).append("=").append(value).append("&");
			}
			url = urlBuilder.toString();
			// 去除多余的&
			url = url.substring(0, url.length() - 1);
		}
		//3.定义请求对象  发起请求
		HttpGet httpGet = new HttpGet(url);
		// 2. 如果代理ip和端口不为空，设置代理
		if (StringUtils.isNotEmpty(proxyIp) && StringUtils.isNotEmpty(proxyPort)) {
			HttpHost proxy = new HttpHost(proxyIp, Integer.parseInt(proxyPort), "http");
			RequestConfig requestConfig = RequestConfig.custom().setSocketTimeout(10000).setConnectTimeout(10000).setProxy(proxy).build();
			httpGet.setConfig(requestConfig);
		}

		//5.发起请求
		try {
			CloseableHttpResponse response = httpClient.execute(httpGet);
			result = EntityUtils.toString(response.getEntity(), charset);
			response.close();
			httpClient.close();
		} catch (IOException e) {
			log.error("---> sendHttpGet - 发送请求异常 - {}", e.getMessage());
		}
		return result;
	}


	public static String sendHttpPost(String url, Map<String, Object> params, String proxyIp, String proxyPort) {
		return HttpUtil.sendHttpPost(url, params, null, proxyIp, proxyPort);
	}


	public static String sendHttpPost(String url, Map<String, Object> params, Map<String, String> headers, String proxyIp, String proxyPort) {
		String result = null;
		CloseableHttpClient httpClient = HttpClients.createDefault();

		// 1.定义请求类型
		HttpPost post = new HttpPost(url);
		String charset = "UTF-8";

		// 2. 如果代理ip和端口不为空，设置代理
		if (StringUtils.isNotEmpty(proxyIp) && StringUtils.isNotEmpty(proxyPort)) {
			HttpHost proxy = new HttpHost(proxyIp, Integer.parseInt(proxyPort), "http");
			RequestConfig requestConfig = RequestConfig.custom().setSocketTimeout(10000).setConnectTimeout(10000).setProxy(proxy).build();
			post.setConfig(requestConfig);
		}

		// 添加头文件
		if (ObjectUtil.isNotEmpty(headers) && headers.size() > 0) {
			Set<String> headerKeys = headers.keySet();
			for (String key : headerKeys) {
				String value = headers.get(key);
				post.setHeader(key, value);
			}
		}

		// 3.判断用户是否传递参数
		if (null != params) {
			try {
				post.addHeader("Content-Type", "application/json;charset=utf-8");
				// 3.4将实体对象封装到请求对象中
				post.setEntity(new StringEntity(JSON.toJSONString(params), "UTF-8"));
			} catch (Exception e) {
				log.error("---> sendHttpPost - 封装参数异常 - {}", e.getMessage());
			}
		}

		// 4.发送请求
		try {
			CloseableHttpResponse response = httpClient.execute(post);
			result = EntityUtils.toString(response.getEntity(), charset);

			response.close();
			httpClient.close();
		} catch (IOException e) {
			log.error("---> sendHttpPost - 发送请求异常 - {}", e.getMessage());
		}

		return result;
	}


	public static String sendHttpDelete(String url, Map<String, Object> params, Map<String, String> headers, List<String> pathParams, String proxyIp, String proxyPort) {
		String result = null;
		CloseableHttpClient httpClient = HttpClients.createDefault();

		// 1. 如果 url 以 / 结尾,则删除最后一位
		String lastChar = url.substring(url.length() - 1);
		if (Objects.equals(lastChar, "/")) {
			url = url.substring(0, url.length() - 1);
		}

		// 2. 添加路径参数
		StringBuilder urlBuilder = new StringBuilder(url);
		if (ObjectUtil.isNotEmpty(pathParams) && pathParams.size() > 0) {
			for (String param : pathParams) {
				urlBuilder.append("/").append(param);
			}
			url = urlBuilder.toString();
		}

		// 3.判断用户是否传递参数
		if (params != null) { // 如果有参数则需要字符串的拼接
			urlBuilder = new StringBuilder(url);
			urlBuilder.append("?");
			for (Map.Entry<String, Object> entry : params.entrySet()) {
				String key = entry.getKey();
				String value = "";
				if (ObjectUtil.isNotEmpty(entry.getValue())) {
					value = String.valueOf(entry.getValue());
				}
				urlBuilder.append(key).append("=").append(value).append("&");
			}
			url = urlBuilder.toString();
			// 去除多余的&
			url = url.substring(0, url.length() - 1);
		}
		log.error(" --->  sendHttpDelete : url:{}", url);
		// 4. 定义请求类型
		HttpDelete delete = new HttpDelete(url);
		String charset = "UTF-8";

		// 5. 如果代理ip和端口不为空，设置代理
		if (StringUtils.isNotEmpty(proxyIp) && StringUtils.isNotEmpty(proxyPort)) {
			HttpHost proxy = new HttpHost(proxyIp, Integer.parseInt(proxyPort), "http");
			RequestConfig requestConfig = RequestConfig.custom().setSocketTimeout(10000).setConnectTimeout(10000).setProxy(proxy).build();
			delete.setConfig(requestConfig);
		}

		// 6. 添加头文件
		if (ObjectUtil.isNotEmpty(headers) && headers.size() > 0) {
			Set<String> headerKeys = headers.keySet();
			for (String key : headerKeys) {
				String value = headers.get(key);
				delete.setHeader(key, value);
			}
		}

		// 7. 发送请求
		try {
			CloseableHttpResponse response = httpClient.execute(delete);
			result = EntityUtils.toString(response.getEntity(), charset);
			response.close();
			httpClient.close();
		} catch (IOException e) {
			log.error("---> sendHttpDelete - 发送请求异常 - {}", e.getMessage());
		}

		return result;
	}
}

